package com.oswift.gpm.system.filter;

import java.io.IOException;
import java.util.List;

import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.RequestDispatcher;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;

import org.codehaus.jackson.map.ObjectMapper;
import org.springframework.web.context.WebApplicationContext;

import com.oswift.gpm.entity.ErrorBean;
import com.oswift.gpm.entity.LoginBean;
import com.oswift.gpm.entity.MenuBean;
import com.oswift.gpm.entity.MessageBean;
import com.oswift.gpm.service.ILoginService;
import com.oswift.gpm.service.impl.LoginServiceImpl;
import com.oswift.gpm.system.SpringAppContext;
import com.oswift.gpm.system.cache.LoginManager;
import com.oswift.gpm.system.cache.WhiteListManager;
import com.oswift.gpm.utils.Constant;
import com.oswift.gpm.utils.PageCode;
import com.oswift.utils.cache.ResourceManager;

/**
 *
 * 是否登录、登录超时判断、权限鉴权
 *
 * @author zhuou
 * @version C03 2013-11-1
 * @since OSwift GPM V1.0
 */
public class AuthenticateFilter implements Filter
{
    @Override
    public void destroy()
    {
    }

    @Override
    public void doFilter(ServletRequest request, ServletResponse response,
            FilterChain filter) throws IOException, ServletException
    {
        HttpServletRequest req = (HttpServletRequest) request;

        // 是否已经登录
        HttpSession session = req.getSession();
        Object sessionObj = session.getAttribute(Constant.SESSION_KEY);
        if (null == session || null == sessionObj)
        {
            String reqMethod = req.getHeader(Constant.AJAX_HEAD_KEY);

            // 是否是ajax请求
            if (Constant.AJAX_HEAD_VALUES.equalsIgnoreCase(reqMethod))
            {
                MessageBean messBean = new MessageBean();
                messBean.setCode(PageCode.SESSION_OVERTIME);
                messBean.setContent(ResourceManager
                        .getValue(PageCode.SESSION_OVERTIME));
                ObjectMapper jsonMap = new ObjectMapper();
                outRespString(jsonMap.writeValueAsString(messBean), response);
            }
            else
            {
                // 跳转到登录页面
                RequestDispatcher dispatcher = request
                        .getRequestDispatcher(Constant.LOGIN_PAGE);
                dispatcher.forward(request, response);
            }
        }
        else
        {
            try
            {
                String reqUrl = req.getRequestURI();
                String contextPath = req.getContextPath();
                if (!"".equals(contextPath))
                {
                    reqUrl = reqUrl.substring(contextPath.length());
                }
                // reqUrl = reqUrl.substring(reqUrl.lastIndexOf("/") + 1);

                // 如果在白名单中，则不做权限鉴权
                boolean isExist = WhiteListManager.isExist(reqUrl);

                // 不在白名单中
                if (!isExist)
                {
                    LoginBean loginBean = LoginManager.getLoginBean(String
                            .valueOf(sessionObj));

                    // 获取spring注入WebAppContext
                    WebApplicationContext WebAppContext = SpringAppContext
                            .getWebAppContext();
                    ILoginService loginService = WebAppContext.getBean(
                            "loginService", LoginServiceImpl.class);

                    List<MenuBean> bean = loginService.getMenu(loginBean
                            .getUserId(), loginBean.getSystemId(), reqUrl);

                    // 取数据库中鉴权,如果存在，则表明有访问权限
                    if (null != bean && !bean.isEmpty())
                    {
                        filter.doFilter(request, response);
                    }
                    else
                    // 取数据库中鉴权,如果不存在，则表明没访问权限
                    {
                        String reqMethod = req
                                .getHeader(Constant.AJAX_HEAD_KEY);
                        if (Constant.AJAX_HEAD_VALUES
                                .equalsIgnoreCase(reqMethod))
                        {
                            MessageBean messBean = new MessageBean();
                            messBean.setCode(PageCode.NO_POWER);
                            messBean.setContent(ResourceManager
                                    .getValue(PageCode.NO_POWER));
                            ObjectMapper jsonMap = new ObjectMapper();
                            outRespString(jsonMap.writeValueAsString(messBean),
                                    response);
                        }
                        else
                        {
                            ErrorBean messBean = new ErrorBean();
                            messBean.setCode(PageCode.NO_POWER);
                            messBean.setMessInfo(ResourceManager
                                    .getValue(PageCode.NO_POWER));
                            request.setAttribute("bean", messBean);
                            // 跳转到登录页面
                            RequestDispatcher dispatcher = request
                                    .getRequestDispatcher(Constant.ERROR_PAGE);
                            dispatcher.forward(request, response);
                        }
                    }
                }
                else
                // 在白名单中,则直接跳转到访问页面
                {
                    filter.doFilter(request, response);
                }
            }
            catch (Exception e)
            {
                String reqMethod = req.getHeader(Constant.AJAX_HEAD_KEY);
                if (Constant.AJAX_HEAD_VALUES.equalsIgnoreCase(reqMethod))
                {
                    MessageBean messBean = new MessageBean();
                    messBean.setCode(PageCode.COMMON_ERROR);
                    messBean.setContent(e.getMessage());
                    ObjectMapper jsonMap = new ObjectMapper();
                    outRespString(jsonMap.writeValueAsString(messBean),
                            response);
                }
                else
                {
                    ErrorBean messBean = new ErrorBean();
                    messBean.setCode(PageCode.COMMON_ERROR);
                    messBean.setMessInfo(e.getMessage());
                    // 跳转到登录页面
                    RequestDispatcher dispatcher = request
                            .getRequestDispatcher(Constant.ERROR_PAGE);
                    dispatcher.forward(request, response);
                }
            }
        }
    }

    @Override
    public void init(FilterConfig arg) throws ServletException
    {
    }

    /**
     *
     * 将数据写入到客户端
     *
     * @author Administrator
     * @param str
     */
    public void outRespString(String str, ServletResponse response)
    {
        response.setContentType("text/html");
        response.setCharacterEncoding("utf-8");

        try
        {
            response.getWriter().println(str);
            response.getWriter().flush();
        }
        catch (IOException e)
        {
            // 异常抛弃
            e.printStackTrace();
        }
    }
}
